/*
Share icon
在使用 JavaScript 中的  setTimeout  函数时，应该注意到一些浏览器的系统会进行“系统补偿（system throttling）”，
也称为“系统平滑过渡（system smoothness transition）”，以提高 CPU 效率，减少电池的耗电等问题。
这些系统会检查浏览器中是否存在大量的  setTimeout  或  setInterval  函数，如果存在，则可能导致等待时间变长。
为了解决这个问题，浏览器可能会自动在  setTimeout  函数的等待时间上添加一些额外的时间，例如在一些浏览器中会自动添加 4ms 的额外时间。

这个补偿时间并不是在所有浏览器中都存在，而是因浏览器而异。当然也并不是每一次都会被添加，只有当浏览器检测到需要使用系统补偿时才会进行添加，
所以在实际开发中，我们并不能完全依靠系统补偿时间，而是需要尽可能合理地设置  setTimeout  函数的等待时间来避免这个问题的发生。
 */
// * 系统补偿时间 关键在于不直接输入时间而是通过计算时间
function _timerSetInterval(fn, delay, ...args) {
    let current = Date.now();
    let timer = null;

    const task = () => {
        current += delay;
        timer = setTimeout(() => {
            fn.apply(this, args);
            task();
        }, current - Date.now());
    };

    task();
    return () => clearTimeout(timer);
}

// _timerSetInterval(console.log, 1000,'1')


function accurateTimeOut(fn,delay,...args) {
    let startTime = Date.now()
    // 执行次数
    let count = 0
    let timer = null
    let task = () => {
        let offset = Date.now() - (startTime + delay * count)
        console.log(`第${count + 1}次系统延时`,offset)
        timer = setTimeout(()=>{
            fn.apply(this,args)
            task()
        },delay - offset)
    }
    task()
    // 返回停止timeout的函数
    return () => clearTimeout(timer);
}
const stop = accurateTimeOut(() => console.log(123), 1000)
//
setTimeout(() => {
    stop()
}, 5000);
